package edu.cuit.campus.config;

import edu.cuit.campus.web.converter.JobConverter;
import edu.cuit.campus.web.interceptor.RoleInterceptor;
import edu.cuit.campus.web.interceptor.RoleInterceptor2;
import edu.cuit.campus.web.interceptor.RoleInterceptor3;
import org.hibernate.validator.HibernateValidator;
import org.springframework.context.MessageSource;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.support.ReloadableResourceBundleMessageSource;
import org.springframework.format.FormatterRegistry;
import org.springframework.validation.Validator;
import org.springframework.validation.beanvalidation.LocalValidatorFactoryBean;
import org.springframework.web.multipart.MultipartResolver;
import org.springframework.web.multipart.support.StandardServletMultipartResolver;
import org.springframework.web.servlet.config.annotation.*;
import org.springframework.web.servlet.view.InternalResourceViewResolver;

/**
 * 配置spring Servlet WebApplicationContext(Spring mvc)
 *
 * @author <a href="mailto:1020zhaodan@163.com">Adan</a>
 * @version 1.0
 * @date 2025/8/15 10:02
 */
@Configuration
@ComponentScan(basePackages = "edu.cuit.campus.web")
@EnableWebMvc //以注解驱动spring mvc(其中已经装配有HandlerMapping及HandlerAdapter等 )
public class SpringServletApplicationContextConfig implements WebMvcConfigurer {

    /**
     * 视图解析器(非必须)
     * @param registry 通过该注册机注册视图解析器
     */
    @Override
    public void configureViewResolvers(ViewResolverRegistry registry) {
        var viewResolver = new InternalResourceViewResolver("/WEB-INF/pages/", ".jsp");
        registry.viewResolver(viewResolver);
    }

    /**
     * 配置静态资源放行
     */
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/**") //静态资源uri
                .addResourceLocations("/public/", "/static/", "/");
    }

    @Override
    public Validator getValidator() {
        var validator = new LocalValidatorFactoryBean();
        validator.setProviderClass(HibernateValidator.class);
        validator.setValidationMessageSource(messageResource());
        return validator;
    }

    /**
     * 全局跨域设置
     */
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("/**")
                .allowedOrigins("http://localhost:63342")
                .allowedMethods("GET", "POST", "PUT", "DELETE", "OPTIONS")
                .allowedHeaders("Content-Type")
                .maxAge(3600)
                .allowCredentials(true);
    }

    /**
     * 资源解析器
     */
    @Bean
    public ReloadableResourceBundleMessageSource messageResource() {
        var messageResource = new ReloadableResourceBundleMessageSource();
        //如果不指定,默认会去classpath下的messages.properties配置文件
        messageResource.setBasename("classpath:message-validation");
        messageResource.setDefaultEncoding("utf-8");
        messageResource.setCacheSeconds(60);
        return messageResource;
    }

    /**
     * 配置文件上传解析器
     */
    @Bean
    public MultipartResolver multipartResolver(){
        return new StandardServletMultipartResolver();
    }

    /**
     * 配置拦截器
     */
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new RoleInterceptor())
                .addPathPatterns("/company/**").order(1);//拦截请求的url,默认表示拦截所有请求

        registry.addInterceptor(new RoleInterceptor2())
                .addPathPatterns("/company/find").order(2);

        registry.addInterceptor(new RoleInterceptor3())
                .addPathPatterns("/company/find").order(3); //order表示拦截器的顺序，默认按照注册顺序执行
    }

    /**
     * 添加类型转换器/formatter
     */
    @Override
    public void addFormatters(FormatterRegistry registry) {
        registry.addConverter(new JobConverter());
    }

    @Bean
    public MessageSource messageSource(){
        var message = new ReloadableResourceBundleMessageSource();
        //如果不指定,默认会去classpath下加载messages.properties配置文件
        message.setBasename("classpath:message");
        message.setDefaultEncoding("utf-8");
        message.setCacheSeconds(60);
        return message;
    }
}
